home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1993 July / InfoMagic USENET CD-ROM July 1993.ISO / sources / unix / volume19 / fbm / part03 < prev    next >
Encoding:
Internet Message Format  |  1989-06-08  |  55.6 KB

  1. Subject:  v19i049:  FBM, image manipulation library, Part03/08
  2. Newsgroups: comp.sources.unix
  3. Sender: sources
  4. Approved: rsalz@uunet.UU.NET
  5.  
  6. Submitted-by: Michael.Mauldin@NL.CS.CMU.EDU
  7. Posting-number: Volume 19, Issue 49
  8. Archive-name: fbm/part03
  9.  
  10. #! /bin/sh
  11. # This is a shell archive.  Remove anything before this line, then unpack
  12. # it by saving it into a file and typing "sh file".  To overwrite existing
  13. # files, type "sh file -c".  You can also feed this as standard input via
  14. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  15. # will see the following message at the end:
  16. #        "End of archive 3 (of 8)."
  17. # Contents:  Features fbhalf.1 fbm.h fbnorm.c fbsample.c flbyte.c
  18. #   flface.c flflyd.c flgifw.c flrdfb.c flread.c raw2fbm.c
  19. # Wrapped by rsalz@fig.bbn.com on Fri Jun  9 08:38:23 1989
  20. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  21. if test -f 'Features' -a "${1}" != "-c" ; then 
  22.   echo shar: Will not clobber existing file \"'Features'\"
  23. else
  24. echo shar: Extracting \"'Features'\" \(4950 characters\)
  25. sed "s/^X//" >'Features' <<'END_OF_FILE'
  26. X************************************************************************
  27. X*   Announcing the "Fuzzy PixMap" (or FBM) image manipulation library  *
  28. X************************************************************************
  29. X
  30. X            Current version 0.94
  31. X
  32. XThe FBM library is now available in Beta test form to interested
  33. Xparties.  This package allows manipulation and conversion of a variety
  34. Xof color and black-and-white image formats.
  35. X
  36. XPhilosophy
  37. X
  38. X    Each program can read any of the understood formats, and
  39. X    can write any of the understood formats that make sense for
  40. X    the image data.
  41. X
  42. X    Programs are designed around specific image operations (sizing,
  43. X    scaling, retoning, halftoning, quantizing, etc.), rather than
  44. X    simply converting from one format to another.  For example,
  45. X    converting a 4bit color GIF file to a 1bit Sun rasterfile
  46. X    takes the following operations:
  47. X    
  48. X        read GIF format
  49. X        map color values to grayscale
  50. X        adjust aspect ratio (1.2 --> 1.0)
  51. X        scale image up to be visible (320x200 --> 640x480 or 1152x864)
  52. X        optionally sharpen the image (edge enhancement)
  53. X        optionally clean up "snow" in image (flip isolated pixels)
  54. X        halftone (Blue noise, Floyd-Steinberg, Jarvis, Threshhold)
  55. X        write Sun rasterfile format.
  56. X
  57. X    So there equivalent pipeline of fbm routines would be:
  58. X    
  59. X    clr2gray < foo.gif | fbnorm | fbext [ args ] | fbhalf [args] > foo.1bit
  60. X    
  61. X    That way you have maximum control over the resulting image size
  62. X    and quality.
  63. X
  64. XInputs the following file formats
  65. X
  66. X  o Sun rasterfiles    (1, 8, or 24 bits, color or grayscale)
  67. X  o GIF files        (1 to 8 bits, color or grayscale)
  68. X  o Amiga IFF files    (except HAM mode)
  69. X  o PCX files
  70. X  o PBM bitmaps
  71. X  o Face files        (CMU format for 1bit files by Bennet Yee)
  72. X  o FBM files        (my own format)
  73. X
  74. X    (automatically determines input format, and uncompresses
  75. X     files compressed using 'compress')
  76. X
  77. XOutputs the following formats
  78. X
  79. X  o Sun rasterfiles
  80. X  o FBM files
  81. X  o GIF files        (mapped color only)
  82. X  o Amiga IFF files    (except HAM mode)
  83. X  o PBM            (1bit files only)
  84. X  o Face format        (1bit files only)
  85. X
  86. XWith input converter for
  87. X
  88. X  o raw images (like Amiga Digi-View files)
  89. X  o Targa        By Ian MacPhedran
  90. X  o PIC            By Ian MacPhedran
  91. X  o QRT            By Butler Hines
  92. X
  93. XWith output converters for
  94. X
  95. X  o PostScript         (1bit or 8bit grayscale files only)
  96. X  o Diablo graphics    (1bit files only)
  97. X  o Targa        By Ian MacPhedran
  98. X
  99. XOperations
  100. X
  101. X  o Extract rectangle (optionally resizing and changing aspect ratio)
  102. X  o Change density and contrast (color and grayscale)
  103. X  o Rotate  90, 180, or 270 degrees
  104. X  o Quantize 24 bit RGB images to 8..256 colors
  105. X        Modified Heckbert median cut
  106. X  o Halftone grayscale using
  107. X        Ulichney's Blue Noise dithering
  108. X        Floyd-Steinberg dithering
  109. X        Jarvis's Constrained averaging
  110. X        Threshholding
  111. X  o Edge Sharpening by Digitial Laplacian (color or grayscale)
  112. X  o Convert color to grayscale (or compute "gray" colormap
  113. X        so grayscale images can be viewed on frame buffers)
  114. X  o Compute histograms of grayscale images
  115. X  o Sample 1bit images to convert to grayscale
  116. X
  117. XStatus
  118. X
  119. X    Beta test release, 0.9.  "Use at your own risk, bug fixes not
  120. X    guaranteed, be happy with minimal documentation."  Bugs reported
  121. X    so far have been fixed.
  122. X
  123. X    Freely available for use, redistribution, incorporation into
  124. X    other code.  Just don't make a profit off it or take my name
  125. X    off of it.
  126. X
  127. X    Written in C for BSD and Mach Unix Systems.
  128. X    Tested on Vaxes, Sun Workstations, IBM RTs and Pyramids.
  129. X    
  130. X    Self contained.  Does not require Sun include files or library
  131. X    routines to manipulate Sun rasters.
  132. X
  133. XAvailability
  134. X
  135. X    Anonymous FTP
  136. X
  137. X    Host:    nl.cs.cmu.edu (128.2.222.56)
  138. X    User:    anonymous
  139. X    Password:    name@site
  140. X    Directory:    /usr/mlm/ftp/
  141. X    Filename:    fbm.tar.Z
  142. X    Transfer:    'image'
  143. X
  144. X    Note: you must 'cd' to /usr/mlm/ftp directly, you cannot access
  145. X    either /usr, or /usr/mlm alone.  Don't forget to specify 'image'
  146. X    format transfer.
  147. X
  148. X    Will be posted to UseNet when the code is stable and
  149. X    the documentation is complete and accurate.
  150. X
  151. XAcknowledgements
  152. X
  153. X    GIF read support written by David Koblas.
  154. X    GIF write support written by David Rowley.
  155. X    Some IFF code by Jerry Morrison and Steve Shaw of Electronic Arts.
  156. X    Edge detection and pixel cleaning by Gary Sherwin and Michael Mauldin
  157. X
  158. XRumours
  159. X
  160. X    Future support is rumoured for TIFF files and MacPaint files.  Also it
  161. X    may someday be able to write all of the formats that it can read.
  162. X
  163. X    All that is needed to incorporate a new format is to write a routine
  164. X    that reads the given image into memory and one that writes it out
  165. X    again.  I will incorporate other code on a "whenever I'm not working
  166. X    on my thesis" basis.
  167. X
  168. XMichael L. Mauldin (Fuzzy)        School of Computer Science
  169. XARPA: Michael.Mauldin@NL.CS.CMU.EDU    Carnegie Mellon University
  170. XPhone: (412) 268-3065            Pittsburgh, PA  15213-3890
  171. END_OF_FILE
  172. if test 4950 -ne `wc -c <'Features'`; then
  173.     echo shar: \"'Features'\" unpacked with wrong size!
  174. fi
  175. # end of 'Features'
  176. fi
  177. if test -f 'fbhalf.1' -a "${1}" != "-c" ; then 
  178.   echo shar: Will not clobber existing file \"'fbhalf.1'\"
  179. else
  180. echo shar: Extracting \"'fbhalf.1'\" \(3597 characters\)
  181. sed "s/^X//" >'fbhalf.1' <<'END_OF_FILE'
  182. X.TH FBHALF 1 07-Mar-89
  183. X.CM 3
  184. X.SH NAME
  185. Xfbhalf \- halftone a grayscale image
  186. X.SH SYNOPSIS
  187. X.nf
  188. Xfbhalf [ -fbct<parm> ] [-s<sharpen> ] [ -C<clean> -N<nbr>]
  189. X       [ -<type> ] [ size ] < 8bit > 1bit
  190. X.fi
  191. X.SH DESCRIPTION
  192. X.PP
  193. XHalftones the 8 bit images and produces a pbm format output.  There are
  194. Xfour halftoning algorithms available: Ulichney's "blue noise"
  195. Xdithering,  Floyd-Steinberg dithering, Jarvis et al's
  196. X"constrained averaging", and simple theshholding.
  197. XThe default is blue noise, but constrained
  198. Xaveraging works better on line drawings and scanned text (with high
  199. Xvalues of gamma \- near 20).  For some images, Floyd-Steinberg gives a
  200. Xtighter, more pleasing pattern than blue noise, but blue noise is more
  201. Xrobust and far less likely to produce significant artifacts.
  202. X.sp
  203. XThe size argument is a maximum number of pixels.  If given,
  204. X.I fbhalf
  205. Xwill resize the image so the width is the largest multiple of 8 such
  206. Xthat the width times the height is less than or equal to the specified
  207. Xsize.  The default is to produce output the same size as the input.
  208. X.SH OPTIONS
  209. X.TP
  210. X.BR -f
  211. X.I Floyd-Steinberg
  212. Xhalftoning.  Using 7-5-3-1 weights.
  213. X.TP
  214. X.BR -b<noise>
  215. X.I Blue noise,
  216. Xwith <noise> percent random weights.  As per Robert Ulichney's PhD
  217. Xthesis.
  218. X.TP
  219. X.BR -c<gamma>
  220. X.I constrained-average
  221. Xhalftoning.  As per Jarvis.  Good for line drawings and graphic art
  222. Xwith a gamma of about 20.
  223. X.TP
  224. X.BR -t<threshhold>
  225. X.I Floyd-simple threshholding,
  226. Xpixels greater than <threshhold> are set to white,
  227. Xand those less than or equal to <threshhold> are set to black.
  228. X.TP
  229. X.BR <size>
  230. X.I number of pixels,
  231. Xspecifies a desired number of output pixels.
  232. XThe actual size used will have an aspect ratio of 1.0 and a width which
  233. Xis the largest possible multiple of 8 so that the image has less than
  234. Xor equal the specified number of pixels.
  235. XThis is a positional argument.
  236. X.TP
  237. X.BR -s<beta>
  238. X.I sharpening,
  239. Xspecifies a certain amount of sharpening after resizing but
  240. Xbefore halftoning.  The default is no sharpening.
  241. X.TP
  242. X.BR -C<num>, -N<num>
  243. X.I clean
  244. Ximage by flipping isolated pixels.  A pixel is isolated if there are
  245. Xfwer than C like colored pixels in the nearby NxN square.  This option
  246. Xcan get rid of "snow" in line art images halftoned by the Jarvis
  247. Xconstrained image halftoning.
  248. X.TP
  249. X.BR -B
  250. X.I face
  251. Xformat, as used by Bennet Yee's
  252. X.I face
  253. Xprogram at CMU. 
  254. X.TP
  255. X.BR -F
  256. X.I FBM,
  257. Xformat (by default, the default).  You are guaranteed not
  258. Xto lose information by specifying FBM as the default.
  259. X.TP
  260. X.BR -G
  261. X.I GIF,
  262. XCompuserve GIF format.
  263. X.TP
  264. X.BR -I
  265. X.I IFF
  266. Xformat, interleaved bitmaps (ILBM), used by Amigas.
  267. X.TP
  268. X.BR -P
  269. X.I PBM,
  270. XJef Poskanzer's bitmap format.
  271. X.TP
  272. X.BR -S
  273. X.I sun,
  274. XSun rasterfiles (not run length encoded).
  275. X.SH EXAMPLE
  276. X.PP
  277. XGiven an 8bit sun rasterfile, halftone using Blue Noise and sharpen
  278. Xwith beta of 8.  Output a Sun 1bit rasterfile:
  279. X.sp
  280. X    % fbhalf -S -s8 < foo.8bit > foo.1bit
  281. X.sp
  282. XUsing Floyd-Steinberg halftoning, convert a color GIF file to a PBM
  283. Xbitmap with about 300,000 pixels.  Sharpen slightly with a beta of 2.0:
  284. X.sp
  285. X    % clr2gray < foo.gif | fbhalf -P -s2.0 300000 > foo.pbm
  286. X.SH SEE ALSO
  287. Xfbm(1) for general discussion, pbm(1) for PBM routines.
  288. X.SH BUGS
  289. XOn the 386i, the sharpening option causes a core dump.  As a workaround
  290. Xyou can use the fbsharp(1) command prioer to running fbhalf(1).
  291. X.SH HISTORY
  292. XCopyright (c) 1989 by Michael L. Mauldin.  
  293. XPermission is granted to use this program in whole or in part provided
  294. Xthat you do not sell it for profit and that this copyright notice is
  295. Xretained unchanged.
  296. X.TP
  297. X07-Mar-89  Michael L. Mauldin at Carnegie Mellon University
  298. XBeta release (version 0.9) mlm@cs.cmu.edu
  299. END_OF_FILE
  300. if test 3597 -ne `wc -c <'fbhalf.1'`; then
  301.     echo shar: \"'fbhalf.1'\" unpacked with wrong size!
  302. fi
  303. # end of 'fbhalf.1'
  304. fi
  305. if test -f 'fbm.h' -a "${1}" != "-c" ; then 
  306.   echo shar: Will not clobber existing file \"'fbm.h'\"
  307. else
  308. echo shar: Extracting \"'fbm.h'\" \(3931 characters\)
  309. sed "s/^X//" >'fbm.h' <<'END_OF_FILE'
  310. X/*****************************************************************
  311. X * fbm.h: FBM Library 0.9 (Beta Test)  07-Mar-89  Michael Mauldin
  312. X *
  313. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  314. X * use this file in whole or in part provided that you do not sell it
  315. X * for profit and that this copyright notice is retained unchanged.
  316. X *
  317. X * fbm.h: Fuzzy Bitmap Definition
  318. X *
  319. X * USAGE
  320. X *    # include <fbm.h>
  321. X *
  322. X * EDITLOG
  323. X *    LastEditDate = Tue Mar  7 19:52:53 1989 - Michael Mauldin
  324. X *    LastFileName = /usr2/mlm/src/misc/fbm/fbm.h
  325. X *
  326. X * HISTORY
  327. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  328. X *    Beta release (version 0.9) mlm@cs.cmu.edu.
  329. X *
  330. X * 20-Aug-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  331. X *    Created.
  332. X *****************************************************************/
  333. X
  334. X# define FBM_MAX_TITLE        80        /* For title and credits */
  335. X
  336. X# define BLACK            0        /* For 8bit files */
  337. X# define WHITE            255        /* For 8bit files */
  338. X# define BYTE            256        /* For 8bit files */
  339. X
  340. X# define BIG            1        /* msb first byte order */
  341. X# define LITTLE            0        /* lsb first byte order */
  342. X
  343. X# define BYTESPERLINE        32        /* For PostScript output */
  344. X
  345. X# define BLANKS        "                                             "
  346. X# define SKIPARG    while (*++(*argv)); --(*argv)
  347. X# define CLRARG        strncpy (*argv, BLANKS, strlen (*argv)); \
  348. X            while (*++(*argv)); --(*argv)
  349. X
  350. X# define FMT_ATK    1    /*   Andrew toolkit raster format */
  351. X# define FMT_FACE    2    /*   Bennet Yee's 1bit Face format */
  352. X# define FMT_FBM    3    /* + Fuzzy bitmap format */
  353. X# define FMT_GIF    4    /*   Compuserve Graphics Interchange */
  354. X# define FMT_IFF    5    /*   Amiga Interchange Format File */
  355. X# define FMT_LEAF    6    /*   InterLeaf image format */
  356. X# define FMT_MCP    7    /*   Macpaint format */
  357. X# define FMT_PBM    8    /*   Poskanzer 1bit format */
  358. X# define FMT_PCX    9    /*   PCX format */
  359. X# define FMT_SUN    10    /* + Sun rasterfile */
  360. X# define FMT_TIFF    11    /*   Tagged IFF, Next, Macintosh */
  361. X# define FMT_X11    12    /*   X11 format */
  362. X
  363. X# define FMTCHAR ".ABFGILMPZSTX"
  364. X
  365. X# define DEF_8BIT    FMT_FBM
  366. X# define DEF_1BIT    FMT_SUN
  367. X
  368. X/* An FBM bitmap header in memory */
  369. Xtypedef struct fbm_hdr_struct {
  370. X    int    cols;            /* Width in pixels */
  371. X    int    rows;            /* Height in pixels */
  372. X    int    planes;            /* Depth (1 for B+W, 3 for RGB) */
  373. X    int    bits;            /* Bits per pixel */
  374. X    int    physbits;        /* Bits to store each pixel */
  375. X    int    rowlen;            /* Length of a row in bytes */
  376. X    int    plnlen;            /* Length of a plane in bytes */
  377. X    int    clrlen;            /* Length of color map */
  378. X    double    aspect;            /* ratio of Y to X of one pixel */
  379. X    char    title[FBM_MAX_TITLE];    /* Null terminated title */
  380. X    char    credits[FBM_MAX_TITLE];    /* Null terminated credits */
  381. X} FBMHDR;
  382. X
  383. X# define FBM_MAGIC    "%bitmap"
  384. X# define BM_MAGIC    ('!' << 8 | '!')
  385. X# define PCX_MAGIC    0xa
  386. X# define GIF_MAGIC    "GIF87a"
  387. X# define IFF_MAGIC    "FORM"
  388. X# define SUN_MAGIC    0x59a66a95
  389. X
  390. X/* FBM bitmap headers in files (null terminated 12 character ascii strings) */
  391. Xtypedef struct fbm_filehdr_struct {
  392. X    char    magic[8];        /* 2 bytes FBM_MAGIC number */
  393. X    char    cols[8];        /* Width in pixels */
  394. X    char    rows[8];        /* Height in pixels */
  395. X    char    planes[8];        /* Depth (1 for B+W, 3 for RGB) */
  396. X    char    bits[8];        /* Bits per pixel */
  397. X    char    physbits[8];        /* Bits to store each pixel */
  398. X    char    rowlen[12];        /* Length of a row in bytes */
  399. X    char    plnlen[12];        /* Length of a plane in bytes */
  400. X    char    clrlen[12];        /* Length of colormap in bytes */
  401. X    char    aspect[12];        /* ratio of Y to X of one pixel */
  402. X    char    title[FBM_MAX_TITLE];    /* Null terminated title */
  403. X    char    credits[FBM_MAX_TITLE];    /* Null terminated credits */
  404. X} FBMFILEHDR;
  405. X
  406. X/* An FBM bitmap in memory */
  407. Xtypedef struct fbm_struct {
  408. X    FBMHDR hdr;            /* Bitmap header */
  409. X    unsigned char *cm;        /* Pointer to colormap */
  410. X    unsigned char *bm;        /* Pointer to raw bits */
  411. X} FBM;
  412. X
  413. X/* Functions */
  414. Xdouble atof ();
  415. Xchar *strcpy(), *strncpy(), *malloc();
  416. Xlong time (), get_long ();
  417. Xint get_short ();
  418. X
  419. X/* Macro for getting next magic char */
  420. X# define NEXTMCH(F,S,L) (((L) > 0) ? ((L)--, *(S)++) : getc (F))
  421. END_OF_FILE
  422. if test 3931 -ne `wc -c <'fbm.h'`; then
  423.     echo shar: \"'fbm.h'\" unpacked with wrong size!
  424. fi
  425. # end of 'fbm.h'
  426. fi
  427. if test -f 'fbnorm.c' -a "${1}" != "-c" ; then 
  428.   echo shar: Will not clobber existing file \"'fbnorm.c'\"
  429. else
  430. echo shar: Extracting \"'fbnorm.c'\" \(4801 characters\)
  431. sed "s/^X//" >'fbnorm.c' <<'END_OF_FILE'
  432. X/*****************************************************************
  433. X * fbnorm.c: FBM Library 0.9 (Beta test) 07-Mar-89  Michael Mauldin
  434. X *
  435. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  436. X * use this file in whole or in part provided that you do not sell it
  437. X * for profit and that this copyright notice is retained unchanged.
  438. X *
  439. X * fbnorm.c: Normalize contrast and brightness of image
  440. X *
  441. X * USAGE
  442. X *      % fbnorm < image > image2
  443. X *
  444. X * EDITLOG
  445. X *      LastEditDate = Tue Mar  7 19:56:35 1989 - Michael Mauldin
  446. X *      LastFileName = /usr2/mlm/src/misc/fbm/fbnorm.c
  447. X *
  448. X * HISTORY
  449. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  450. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  451. X *
  452. X * 21-Aug-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  453. X *      Created.
  454. X *****************************************************************/
  455. X
  456. X# include <stdio.h>
  457. X# include <math.h>
  458. X# include <ctype.h>
  459. X# include "fbm.h"
  460. X
  461. X# define USAGE \
  462. X    "Usage: fbnorm [ -b<val> -w<val> ] [ -<type> ] < image > image"
  463. X
  464. X#ifndef lint
  465. Xstatic char *fbmid =
  466. X    "$FBM fbnorm.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  467. X#endif
  468. X
  469. Xmain (argc, argv)
  470. Xchar *argv[];
  471. X{ FBM image;
  472. X  register unsigned char *bmptr, *tail;
  473. X  register int j, k, ch, size, cnt;
  474. X  int min = -1, max = -1, cutoff;
  475. X  int hist[BYTE];
  476. X  double blackp = -1.0, whitep = -1.0;    /* Percent */
  477. X  int outtype = FMT_FBM;
  478. X
  479. X  /* Get the options */
  480. X  while (--argc > 0 && (*++argv)[0] == '-')
  481. X  { while (*++(*argv))
  482. X    { switch (**argv)
  483. X      { case 'b':       blackp = atof (*argv+1); SKIPARG; break;
  484. X        case 'w':       whitep = atof (*argv+1); SKIPARG; break;
  485. X    case 'A':    outtype = FMT_ATK; break;
  486. X    case 'B':    outtype = FMT_FACE; break;
  487. X    case 'F':    outtype = FMT_FBM; break;
  488. X    case 'G':    outtype = FMT_GIF; break;
  489. X    case 'I':    outtype = FMT_IFF; break;
  490. X    case 'L':    outtype = FMT_LEAF; break;
  491. X    case 'M':    outtype = FMT_MCP; break;
  492. X    case 'P':    outtype = FMT_PBM; break;
  493. X    case 'S':    outtype = FMT_SUN; break;
  494. X    case 'T':    outtype = FMT_TIFF; break;
  495. X    case 'X':    outtype = FMT_X11; break;
  496. X    case 'Z':    outtype = FMT_PCX; break;
  497. X        default:        fprintf (stderr, "%s\n", USAGE);
  498. X                        exit (1);
  499. X      }
  500. X    }
  501. X  }
  502. X
  503. X  if (argc == 1)
  504. X  { blackp = whitep = atof (argv[0]); }
  505. X  else if (argc == 2)
  506. X  { min = atoi (argv[0]); max = atoi (argv[1]); }
  507. X  else if (argc > 2)
  508. X  { fprintf (stderr, "%s\n", USAGE);
  509. X    exit (1);
  510. X  }
  511. X  
  512. X  /* Clear the memory pointer so alloc_fbm won't be confused */
  513. X  image.cm  = image.bm  = (unsigned char *) NULL;
  514. X
  515. X  /* Now read in the image */
  516. X  if (read_bitmap (&image, (char *) NULL))
  517. X  { 
  518. X    /* Check input type */
  519. X    if (image.hdr.physbits != 8)
  520. X    { fprintf (stderr,
  521. X           "Can't resize images with %d physical bits per pixel\n",
  522. X           image.hdr.physbits);
  523. X      exit (1);
  524. X    }
  525. X
  526. X    /* Set default tail sizes */
  527. X    if (image.hdr.planes > 1)        /* Color defaults */
  528. X    { if (blackp < 0.0) blackp = 0.5;
  529. X      if (whitep < 0.0) whitep = 0.5;
  530. X    }
  531. X    else                /* Bw defaults */
  532. X    { if (blackp < 0.0) blackp = 2.0;
  533. X      if (whitep < 0.0) whitep = 1.0;
  534. X    }
  535. X
  536. X    size = image.hdr.rows * image.hdr.cols * image.hdr.planes;
  537. X
  538. X    /* Calculate min and max (if not given as arguments) */
  539. X    if (min < 0 || max < 0)
  540. X    {
  541. X      /* Compute histogram */
  542. X      for (ch=0; ch<BYTE; ch++)
  543. X      { hist[ch] = 0; }
  544. X  
  545. X      for (k=0; k<image.hdr.planes; k++)
  546. X      { for (j=0; j< image.hdr.rows; j++)
  547. X        { bmptr = &(image.bm[k*image.hdr.plnlen + j*image.hdr.rowlen]);
  548. X          tail = bmptr + image.hdr.cols;
  549. X          
  550. X          while (bmptr < tail)
  551. X          { hist[*bmptr++]++; }
  552. X        }
  553. X      }
  554. X
  555. X      /* Take off 'blackp' percent of darkest pixels */      
  556. X      cutoff = size * blackp / 100.0;
  557. X
  558. X      for (ch=0, cnt=0; ch<BYTE; ch++)
  559. X      { if ((cnt += hist[ch]) > cutoff)
  560. X        { min = ch; break; }
  561. X      }
  562. X
  563. X      /* Take off 'whitep' percent of darkest pixels */      
  564. X      cutoff = size * whitep / 100.0;
  565. X
  566. X      for (ch = BYTE-1, cnt=0; ch >= 0; ch--)
  567. X      { if ((cnt += hist[ch]) > cutoff)
  568. X        { max = ch; break; }
  569. X      }
  570. X    }
  571. X      
  572. X    fprintf (stderr, "Normalizing: \"%s\" <%d,%d> ==> <0..255>\n",
  573. X             image.hdr.title[0] ? image.hdr.title : "(untitled)", min, max);
  574. X
  575. X    bmptr = image.bm;
  576. X    tail = bmptr+size;
  577. X
  578. X    while (bmptr < tail)
  579. X    { ch = *bmptr;
  580. X
  581. X      if (ch <= min)
  582. X      { ch = 0; }
  583. X      else if (ch >= max)
  584. X      { ch = 255; }
  585. X      else
  586. X      { ch = (ch - min) * 255 / (max - min); }
  587. X
  588. X       if (ch < 0 || ch > 255)
  589. X       { fprintf (stderr, "raw %d, min %d, max %d, out %d\n",
  590. X                  *bmptr, min, max, ch);
  591. X       }
  592. X
  593. X      *bmptr++ = ch;
  594. X    }
  595. X    
  596. X    /* The image is now an 8bit per pixel image */
  597. X    image.hdr.bits = 8;
  598. X
  599. X    /* Write it out */
  600. X    write_bitmap (&image, stdout, outtype);
  601. X  }
  602. X  else
  603. X  { exit (1); }
  604. X  
  605. X  exit (0);
  606. X}
  607. END_OF_FILE
  608. if test 4801 -ne `wc -c <'fbnorm.c'`; then
  609.     echo shar: \"'fbnorm.c'\" unpacked with wrong size!
  610. fi
  611. # end of 'fbnorm.c'
  612. fi
  613. if test -f 'fbsample.c' -a "${1}" != "-c" ; then 
  614.   echo shar: Will not clobber existing file \"'fbsample.c'\"
  615. else
  616. echo shar: Extracting \"'fbsample.c'\" \(4262 characters\)
  617. sed "s/^X//" >'fbsample.c' <<'END_OF_FILE'
  618. X/*****************************************************************
  619. X * fbsample.c: FBM Library 0.94 (Beta test) 20-May-89  Michael Mauldin
  620. X *
  621. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  622. X * use this file in whole or in part provided that you do not sell it
  623. X * for profit and that this copyright notice is retained unchanged.
  624. X *
  625. X * fbsample.c:  1 bit to 8 bit conversion by sampling
  626. X *
  627. X * USAGE
  628. X *    % fbsample [ title ] < foo.pbm > foo.fbm
  629. X *
  630. X * EDITLOG
  631. X *    LastEditDate = Sat May 20 19:05:33 1989 - Michael Mauldin
  632. X *    LastFileName = /usr2/mlm/src/misc/fbm/fbsample.c
  633. X *
  634. X * HISTORY
  635. X * 20-May-89  Michael Mauldin (mlm) at Carnegie Mellon University
  636. X *    Bug fix from Dave Cohrs <dave@cs.wisc.edu>
  637. X *
  638. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  639. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  640. X *
  641. X *  5-Sep-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  642. X *    Created.
  643. X *****************************************************************/
  644. X
  645. X#include <stdio.h>
  646. X#include <ctype.h>
  647. X#include "fbm.h"
  648. X
  649. Xint width, height;
  650. X
  651. X# define USAGE \
  652. X  "fbsample [ -t'title' -c'credits' -g'grain' -n'nbr' ]\n\
  653. X     [ -<type> ] < bitmap > image"
  654. X
  655. X#ifndef lint
  656. Xstatic char *fbmid =
  657. X    "$FBM fbsample.c <0.94> 20-May-89  (C) 1989 by Michael Mauldin$";
  658. X#endif
  659. X
  660. Xmain(argc, argv)
  661. X  int             argc;
  662. X  char           *argv[];
  663. X{
  664. X  char           *title = NULL, *credits = NULL;
  665. X  register unsigned char *bmp;
  666. X  register int      i, j, r, c, irow, orow, grain=5, nbr=5, sum;
  667. X  int          outtype = DEF_1BIT;
  668. X  FBM          input, output;
  669. X
  670. X  /* Clear the memory pointers so alloc_fbm won't be confused */
  671. X  input.cm  = input.bm  = (unsigned char *) NULL;
  672. X  output.cm = output.bm = (unsigned char *) NULL;
  673. X
  674. X  /* Get the options */
  675. X  while (--argc > 0 && (*++argv)[0] == '-')
  676. X  { while (*++(*argv))
  677. X    { switch (**argv)
  678. X      { case 'g':    grain = atoi (*argv+1); SKIPARG; break;
  679. X        case 'n':    nbr = atoi (*argv+1); SKIPARG; break;
  680. X    case 't':    title = *argv+1; SKIPARG; break;
  681. X    case 'c':    credits = *argv+1; SKIPARG; break;
  682. X    case 'A':    outtype = FMT_ATK; break;
  683. X    case 'B':    outtype = FMT_FACE; break;
  684. X    case 'F':    outtype = FMT_FBM; break;
  685. X    case 'G':    outtype = FMT_GIF; break;
  686. X    case 'I':    outtype = FMT_IFF; break;
  687. X    case 'L':    outtype = FMT_LEAF; break;
  688. X    case 'M':    outtype = FMT_MCP; break;
  689. X    case 'P':    outtype = FMT_PBM; break;
  690. X    case 'S':    outtype = FMT_SUN; break;
  691. X    case 'T':    outtype = FMT_TIFF; break;
  692. X    case 'X':    outtype = FMT_X11; break;
  693. X    case 'Z':    outtype = FMT_PCX; break;
  694. X    default:    fprintf (stderr, "Usage: %s\n", USAGE);
  695. X            exit (1);
  696. X      }
  697. X    }
  698. X  }
  699. X
  700. X  if (grain < 1 || grain > 16)
  701. X  { fprintf (stderr,
  702. X         "Usage: %s\n%s\n",
  703. X         "       (grain must be between 1 and 16)\n");
  704. X    exit (0);
  705. X  }
  706. X
  707. X  /* Read pbm bitmap */
  708. X  if (! read_bitmap (&input, (char *) NULL))
  709. X  { fprintf (stderr, "%s: input garbled or not in PBM format\n", argv[0]);
  710. X    exit(1);
  711. X  }
  712. X
  713. X  if (title == NULL && input.hdr.title[0])
  714. X  { title = input.hdr.title; }
  715. X
  716. X  if (grain > 1)
  717. X  { width = input.hdr.cols / grain;
  718. X    height = input.hdr.rows / grain;
  719. X  }
  720. X  else
  721. X  { width = input.hdr.cols - grain + 1;
  722. X    height = input.hdr.rows - grain + 1;
  723. X  }
  724. X
  725. X  orow = 2 * ((width * 8 + 15) / 16);
  726. X  irow = input.hdr.rowlen;
  727. X
  728. X  fprintf (stderr, "Sample (1bit to 8bit) \"%s\": [%dx%dx1] ==> [%dx%dx8]\n",
  729. X      title ? title : "(untitled)",
  730. X      input.hdr.cols, input.hdr.rows, width, height);
  731. X
  732. X  /* Set up output header */
  733. X  output.hdr.cols = width;
  734. X  output.hdr.rows = height;
  735. X  output.hdr.planes = 1;
  736. X  output.hdr.bits = 8;
  737. X  output.hdr.physbits = 8;
  738. X  output.hdr.rowlen = orow;
  739. X  output.hdr.plnlen = orow * height;
  740. X  output.hdr.aspect = 1.0;
  741. X  output.hdr.clrlen = 0;
  742. X
  743. X  if (title) strcpy (output.hdr.title, title);
  744. X  if (credits) strcpy (output.hdr.credits, credits);
  745. X  
  746. X  alloc_fbm (&output);
  747. X
  748. X  fprintf (stderr, "width %d, height %d, grain %d, nbr %d, irow %d, orow %d\n",
  749. X       width, height, grain, nbr, irow, orow);
  750. X  
  751. X  for (r=0; r<height; r++)
  752. X  { for (c=0; c<width; c++)
  753. X    { sum = 0;
  754. X      bmp = &(input.bm[(r*grain) * irow + (c*grain)]);
  755. X
  756. X      for (j=0; j<nbr; j++, bmp += irow)
  757. X      { for (i=0; i<nbr; i++)
  758. X        { if (bmp[i]) sum++; }
  759. X      }
  760. X
  761. X      if (sum > 255) sum = 255;
  762. X      
  763. X      output.bm[r * orow + c] = sum;
  764. X    }
  765. X  }
  766. X
  767. X  write_bitmap (&output, stdout, outtype);
  768. X
  769. X  exit (0);
  770. X}
  771. END_OF_FILE
  772. if test 4262 -ne `wc -c <'fbsample.c'`; then
  773.     echo shar: \"'fbsample.c'\" unpacked with wrong size!
  774. fi
  775. # end of 'fbsample.c'
  776. fi
  777. if test -f 'flbyte.c' -a "${1}" != "-c" ; then 
  778.   echo shar: Will not clobber existing file \"'flbyte.c'\"
  779. else
  780. echo shar: Extracting \"'flbyte.c'\" \(4126 characters\)
  781. sed "s/^X//" >'flbyte.c' <<'END_OF_FILE'
  782. X/*****************************************************************
  783. X * flbyte.c: FBM Library 0.94 (Beta test) 20-May-89  Michael Mauldin
  784. X *
  785. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  786. X * use this file in whole or in part provided that you do not sell it
  787. X * for profit and that this copyright notice is retained unchanged.
  788. X *
  789. X * flbyte.c: 
  790. X *
  791. X * CONTENTS
  792. X *    get_long (rfile, order)
  793. X *    get_short (rfile, order)
  794. X *    put_long (long, wfile, order)
  795. X *    put_short (word, wfile, order)
  796. X *    machine_byte_order ()
  797. X *
  798. X *    order    BIG    msb first (Sun, IBM-RT, 68000)
  799. X *        LITTLE    lsb first (Vax, 6502)
  800. X *
  801. X * EDITLOG
  802. X *    LastEditDate = Sat May 20 19:11:04 1989 - Michael Mauldin
  803. X *    LastFileName = /usr2/mlm/src/misc/fbm/flbyte.c
  804. X *
  805. X * HISTORY
  806. X * 20-May-89  Michael Mauldin (mlm) at Carnegie Mellon University
  807. X *    Bug fix from Dave Cohrs <dave@cs.wisc.edu>
  808. X *
  809. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  810. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  811. X *
  812. X * 12-Nov-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  813. X *    Created.
  814. X *****************************************************************/
  815. X
  816. X# include <stdio.h>
  817. X# include "fbm.h"
  818. X
  819. X/****************************************************************
  820. X * get_long: get a long integer from a file
  821. X ****************************************************************/
  822. X
  823. X#ifndef lint
  824. Xstatic char *fbmid =
  825. X    "$FBM flbyte.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  826. X#endif
  827. X
  828. Xlong
  829. Xget_long (file, order)
  830. XFILE *file;
  831. Xint order;
  832. X{ register long word;
  833. X
  834. X  if (order == BIG)
  835. X  { word = fgetc (file) & 0x0ff;
  836. X    word = word << 8 | (fgetc (file) & 0x0ff);
  837. X    word = word << 8 | (fgetc (file) & 0x0ff);
  838. X    word = word << 8 | (fgetc (file) & 0x0ff);
  839. X  }
  840. X  else
  841. X  { word = fgetc (file) & 0x0ff;
  842. X    word = word | ((fgetc (file) & 0x0ff) << 8);
  843. X    word = word | ((fgetc (file) & 0x0ff) << 16);
  844. X    word = word | ((fgetc (file) & 0x0ff) << 24);
  845. X  }
  846. X
  847. X  return (word);
  848. X}
  849. X
  850. X/****************************************************************
  851. X * put_long: Write a long integer to a file
  852. X ****************************************************************/
  853. X
  854. Xput_long (word, file, order)
  855. Xregister long word;
  856. XFILE *file;
  857. Xint order;
  858. X{
  859. X  if (order == BIG)
  860. X  { fputc ((word >> 24) & 0x0ff, file);    /* Put out biggest byte */
  861. X    fputc ((word >> 16) & 0x0ff, file);    /* Put out 2nd byte */
  862. X    fputc ((word >> 8) & 0x0ff, file);    /* Put out 3rd byte */
  863. X    fputc (word & 0x0ff, file);        /* Put out littlest byte */
  864. X  }
  865. X  else
  866. X  { fputc (word & 0x0ff, file);        /* Put out littlest byte */
  867. X    fputc ((word >> 8) & 0x0ff, file);    /* Put out 3rd byte */
  868. X    fputc ((word >> 16) & 0x0ff, file);    /* Put out 2nd byte */
  869. X    fputc ((word >> 24) & 0x0ff, file);    /* Put out biggest byte */
  870. X  }
  871. X}
  872. X
  873. X/****************************************************************
  874. X * get_short: get a short integer from a file
  875. X ****************************************************************/
  876. X
  877. Xget_short (file, order)
  878. XFILE *file;
  879. Xint order;
  880. X{ register int word;
  881. X
  882. X  if (order == BIG)
  883. X  { word = fgetc (file) & 0x0ff;
  884. X    word = word << 8 | (fgetc (file) & 0x0ff);
  885. X  }
  886. X  else
  887. X  { word = fgetc (file) & 0x0ff;
  888. X    word = word | ((fgetc (file) & 0x0ff) << 8);
  889. X  }
  890. X
  891. X  return (word);
  892. X}
  893. X
  894. X/****************************************************************
  895. X * put_short: Write a short integer to a file
  896. X ****************************************************************/
  897. X
  898. Xput_short (word, file, order)
  899. Xregister int word;
  900. XFILE *file;
  901. Xint order;
  902. X{
  903. X  if (order == BIG)
  904. X  { fputc ((word >> 8) & 0x0ff, file);    /* Put out 3rd byte */
  905. X    fputc (word & 0x0ff, file);        /* Put out littlest byte */
  906. X  }
  907. X  else
  908. X  { fputc (word & 0x0ff, file);        /* Put out littlest byte */
  909. X    fputc ((word >> 8) & 0x0ff, file);    /* Put out 3rd byte */
  910. X  }
  911. X}
  912. X
  913. X/****************************************************************
  914. X * machine_byte_order: Return BIG or LITTLE for the current machine
  915. X ****************************************************************/
  916. X
  917. Xmachine_byte_order ()
  918. X{ short testshort;
  919. X  char *teststr = (char*) &testshort;
  920. X
  921. X  teststr[0] = '\1'; teststr[1] = '\0';
  922. X
  923. X  if (testshort == 1)
  924. X  { return (LITTLE); }
  925. X  else
  926. X  { return (BIG); }
  927. X}
  928. END_OF_FILE
  929. if test 4126 -ne `wc -c <'flbyte.c'`; then
  930.     echo shar: \"'flbyte.c'\" unpacked with wrong size!
  931. fi
  932. # end of 'flbyte.c'
  933. fi
  934. if test -f 'flface.c' -a "${1}" != "-c" ; then 
  935.   echo shar: Will not clobber existing file \"'flface.c'\"
  936. else
  937. echo shar: Extracting \"'flface.c'\" \(3670 characters\)
  938. sed "s/^X//" >'flface.c' <<'END_OF_FILE'
  939. X/*****************************************************************
  940. X * flface.c: FBM Library 0.9 (Beta test) 07-Mar-89  Michael Mauldin
  941. X *
  942. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  943. X * use this file in whole or in part provided that you do not sell it
  944. X * for profit and that this copyright notice is retained unchanged.
  945. X *
  946. X * flface.c: 
  947. X *
  948. X * CONTENTS
  949. X *    write_face (image, stream)
  950. X *    read_face (image, stream, mstr, mlen)
  951. X *    
  952. X *
  953. X * EDITLOG
  954. X *    LastEditDate = Tue Mar  7 19:57:03 1989 - Michael Mauldin
  955. X *    LastFileName = /usr2/mlm/src/misc/fbm/flface.c
  956. X *
  957. X * HISTORY
  958. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  959. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  960. X *
  961. X * 12-Nov-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  962. X *    Created.
  963. X *****************************************************************/
  964. X
  965. X# include <stdio.h>
  966. X# include <math.h>
  967. X# include <ctype.h>
  968. X# include "fbm.h"
  969. X
  970. X/****************************************************************
  971. X * write_face: Write Bennet Yee's face file format
  972. X ****************************************************************/
  973. X
  974. X#ifndef lint
  975. Xstatic char *fbmid =
  976. X    "$FBM flface.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  977. X#endif
  978. X
  979. Xwrite_face (image, stream)
  980. XFBM *image;
  981. XFILE *stream;
  982. X{ register int r, c, word, width, height;
  983. X  register unsigned char *bm;
  984. X
  985. X  width = image->hdr.cols;
  986. X  height = image->hdr.rows;
  987. X
  988. X  put_short (BM_MAGIC, stream, BIG);
  989. X  put_short (width, stream, BIG);
  990. X  put_short (height, stream, BIG);
  991. X  
  992. X  for (r=0; r<height; r++)
  993. X  { word = 0;
  994. X    bm = &(image->bm[r * image->hdr.rowlen]);
  995. X
  996. X    for (c=0; c<width; c++)
  997. X    { word = (word >> 1) | (*bm++ ? 0: ((1 << 15)));
  998. X      if ((c&15) == 15) put_short (word, stream, BIG);
  999. X    }
  1000. X
  1001. X    if (c&15)
  1002. X    { word >>= (16 - (c&15));
  1003. X      put_short (word, stream, BIG);
  1004. X    }
  1005. X  }
  1006. X  
  1007. X  return (1);
  1008. X}
  1009. X
  1010. X/****************************************************************
  1011. X * read_face: Read Bennet Yee's FACE format
  1012. X ****************************************************************/
  1013. X
  1014. Xread_face (image, rfile, mstr, mlen)
  1015. XFBM *image;
  1016. XFILE *rfile;
  1017. Xchar *mstr;
  1018. Xint mlen;
  1019. X{ register unsigned char *bmp;
  1020. X  register int r, c, word, width, height, rowlen, magic;
  1021. X
  1022. X  magic =  (NEXTMCH(rfile,mstr,mlen) & 0xff) << 8;
  1023. X  magic |= (NEXTMCH(rfile,mstr,mlen) & 0xff);
  1024. X
  1025. X  if (magic != BM_MAGIC)
  1026. X  { fprintf (stderr, "Bad magic number %04x, not BM format\n", magic);
  1027. X
  1028. X    fprintf (stderr, "Next 10 chars:");
  1029. X    for (r=0; r<10; r++)
  1030. X    { c = fgetc (rfile); fprintf (stderr, " %03o", c); }
  1031. X    fprintf (stderr, "\n");
  1032. X    return (0);
  1033. X  }
  1034. X  
  1035. X  width = get_short (rfile, BIG);
  1036. X  height = get_short (rfile, BIG);
  1037. X  
  1038. X  if (width > 5000 || height > 5000)
  1039. X  { fprintf (stderr, "Image too big, bogus width %d or height %d maybe?\n",
  1040. X         width, height);
  1041. X    return (0);
  1042. X  }
  1043. X
  1044. X  /* Initialize FBM header and allocate memory for bitmap */
  1045. X  image->hdr.cols = width;
  1046. X  image->hdr.rows = height;
  1047. X  image->hdr.planes = 1;
  1048. X  image->hdr.bits = 1;
  1049. X  image->hdr.physbits = 8;
  1050. X  image->hdr.rowlen = 16 * ((image->hdr.cols + 15) / 16);
  1051. X  image->hdr.plnlen = image->hdr.rowlen * image->hdr.rows;
  1052. X  image->hdr.clrlen = 0;
  1053. X  image->hdr.aspect = 1.0;
  1054. X  image->hdr.title[0] = 0;
  1055. X  image->hdr.credits[0] = 0;
  1056. X
  1057. X  alloc_fbm (image);
  1058. X
  1059. X  /* Now read bits and store them in the proper place in the bitmap */
  1060. X  rowlen = image->hdr.rowlen;
  1061. X
  1062. X  
  1063. X  for (r=0; r<height; r++)
  1064. X  { bmp = &(image->bm[r * rowlen]);
  1065. X
  1066. X    for (c=0; c<width; c++)
  1067. X    { if ((c&15) == 0 && (word = get_short (rfile, BIG)) == EOF)
  1068. X      { fprintf (stderr, "r %d, c %d\n", r, c);
  1069. X        return (0);
  1070. X      }
  1071. X
  1072. X      *bmp++ = ((word & 1) ? BLACK : WHITE);
  1073. X      word >>= 1;
  1074. X    }
  1075. X  }
  1076. X  
  1077. X  return (1);
  1078. X}
  1079. END_OF_FILE
  1080. if test 3670 -ne `wc -c <'flface.c'`; then
  1081.     echo shar: \"'flface.c'\" unpacked with wrong size!
  1082. fi
  1083. # end of 'flface.c'
  1084. fi
  1085. if test -f 'flflyd.c' -a "${1}" != "-c" ; then 
  1086.   echo shar: Will not clobber existing file \"'flflyd.c'\"
  1087. else
  1088. echo shar: Extracting \"'flflyd.c'\" \(4361 characters\)
  1089. sed "s/^X//" >'flflyd.c' <<'END_OF_FILE'
  1090. X/*****************************************************************
  1091. X * flflyd.c: FBM Library 0.94 (Beta test) 20-May-89  Michael Mauldin
  1092. X *
  1093. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  1094. X * use this file in whole or in part provided that you do not sell it
  1095. X * for profit and that this copyright notice is retained unchanged.
  1096. X *
  1097. X * flflyd.c: 
  1098. X *
  1099. X * CONTENTS
  1100. X *    floyd_fbm (input, output)
  1101. X *
  1102. X * EDITLOG
  1103. X *    LastEditDate = Sat May 20 19:13:12 1989 - Michael Mauldin
  1104. X *    LastFileName = /usr2/mlm/src/misc/fbm/flflyd.c
  1105. X *
  1106. X * HISTORY
  1107. X * 20-May-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1108. X *    Bug fix from Dave Cohrs <dave@cs.wisc.edu>
  1109. X *
  1110. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1111. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  1112. X *
  1113. X * 12-Nov-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  1114. X *    Created.
  1115. X *****************************************************************/
  1116. X
  1117. X# include <stdio.h>
  1118. X# include <math.h>
  1119. X# include <ctype.h>
  1120. X# include "fbm.h"
  1121. X
  1122. X/*****************************************************************
  1123. X * floyd_fbm: Classical Floyd-Steinberg Halftoning
  1124. X *
  1125. X * REFERENCES
  1126. X *    Digital Halftoning, by Robert Ulichney (1986 MIT Press)
  1127. X *****************************************************************/
  1128. X
  1129. X# define RAND(RN) (((seed = 1103515245 * seed + 12345) >> 12) % (RN))
  1130. X# define INITERR(X,Y) \
  1131. X    (((int) X) - (((int) Y)?WHITE:BLACK) + ((WHITE/2)-((int) X))/2)
  1132. X
  1133. X#ifndef lint
  1134. Xstatic char *fbmid =
  1135. X    "$FBM flflyd.c <0.94> 20-May-89  (C) 1989 by Michael Mauldin$";
  1136. X#endif
  1137. X
  1138. Xfloyd_fbm (input, output)
  1139. XFBM *input, *output;
  1140. X{ register unsigned char *bmp, *obm;
  1141. X  register int i, j, rowlen, gray, error, w, h, den, outrow;
  1142. X  int *lerr, *cerr, *terr;
  1143. X  register int seed = 0;
  1144. X
  1145. X  if (input->hdr.planes != 1)
  1146. X  { fprintf (stderr, "floyd_fbm: can't halftone color images\n");
  1147. X    return (0);
  1148. X  }
  1149. X
  1150. X  fprintf (stderr, "Floyd-Steinberg halftoning\n");
  1151. X
  1152. X  /* Allocate output */
  1153. X  free_fbm (output);
  1154. X  output->hdr = input->hdr;
  1155. X  output->hdr.bits = 1;
  1156. X  output->hdr.physbits = 8;
  1157. X  outrow = 16 * ((input->hdr.cols + 15) / 16); /* Pad to even byte boundary */
  1158. X  output->hdr.rowlen = outrow;
  1159. X  output->hdr.plnlen = outrow*output->hdr.rows;
  1160. X  alloc_fbm (output);
  1161. X
  1162. X  w = input->hdr.cols;
  1163. X  h = input->hdr.rows;
  1164. X  rowlen = input->hdr.rowlen;
  1165. X  
  1166. X  /* Allocate space for error arrays */
  1167. X  lerr = (int *) malloc (w * sizeof (*lerr));
  1168. X  cerr = (int *) malloc (w * sizeof (*cerr));
  1169. X  for (i=0; i<w; i++) lerr[i] = cerr[i] = 0;
  1170. X
  1171. X  /* The left border */
  1172. X  error = 0;
  1173. X  for (j=0; j<h; j++)
  1174. X  { register int thresh = (WHITE/2 + RAND (129) - 64);
  1175. X
  1176. X    gray = input->bm[j*rowlen] + error;
  1177. X    den = gray > thresh ? WHITE : BLACK;
  1178. X    error = gray - den;
  1179. X    output->bm[j*outrow] = den;
  1180. X  }
  1181. X
  1182. X  /* The right border */
  1183. X  error = 0;
  1184. X  for (j=0; j<h; j++)
  1185. X  { register int thresh = (WHITE/2 + RAND (129) - 64);
  1186. X
  1187. X    gray = input->bm[j*rowlen + (w-1)] + error;
  1188. X    den = gray > thresh ? WHITE : BLACK;
  1189. X    error = gray - den;
  1190. X    output->bm[j*outrow + (w-1)] = den;
  1191. X  }
  1192. X
  1193. X  /* The top border */
  1194. X  error = 0;
  1195. X  for (i=0; i<w; i++)
  1196. X  { register int thresh = (WHITE/2 + RAND (129) - 64);
  1197. X
  1198. X    gray = input->bm[i] + error;
  1199. X    den = gray > thresh ? WHITE : BLACK;
  1200. X    error = gray - den;
  1201. X    output->bm[i] = den;
  1202. X    lerr[i] = INITERR (input->bm[i], den);
  1203. X  }
  1204. X
  1205. X  /*
  1206. X   * Now process the interior bits
  1207. X   *
  1208. X   *  Weights:            1 5 3
  1209. X   *                7 *
  1210. X   */
  1211. X
  1212. X  for (j=1; j<h; j++)
  1213. X  { /* scan left to right */
  1214. X    bmp = &input->bm[j*rowlen];
  1215. X    obm = &output->bm[j*outrow];
  1216. X
  1217. X    cerr[0] = INITERR (bmp[0], obm[0]);
  1218. X
  1219. X    for (i=1; i<w-1; i++)
  1220. X    {
  1221. X      error =  (lerr[i-1] + 5 * lerr[i] + 3 * lerr[i+1] + 7 * cerr[i-1]) / 16;
  1222. X
  1223. X# ifdef DEBUG
  1224. X      if (i > 5 && i < 9 && j > 5 && j < 9)
  1225. X      { fprintf (stderr, "<%2d,%2d>  Input %3d, Error %5d, Output %d\n",
  1226. X         i, j, bmp[i], error, bmp[i] + error > (WHITE/2));
  1227. X    fprintf (stderr, "Errors:   %5d  %5d  %5d\n          %5d      *\n\n", 
  1228. X         lerr[i-1], lerr[i], lerr[i+1], cerr[i-1]);
  1229. X      }
  1230. X# endif
  1231. X
  1232. X      gray = bmp[i] + error;
  1233. X
  1234. X      if (gray > (WHITE/2))
  1235. X      { obm[i] = WHITE;    cerr[i] = gray - WHITE; }
  1236. X      else
  1237. X      { obm[i] = BLACK;    cerr[i] = gray - BLACK; }
  1238. X    }
  1239. X    
  1240. X    /* Set errors for ends of the row */
  1241. X    cerr[0]   = INITERR (bmp[0], obm[0]);
  1242. X    cerr[w-1] = INITERR (bmp[w-1], obm[w-1]);
  1243. X    
  1244. X    /* Swap error buffers */
  1245. X    terr = lerr; lerr = cerr; cerr = terr;
  1246. X  }
  1247. X  
  1248. X  return (1);
  1249. X}
  1250. END_OF_FILE
  1251. if test 4361 -ne `wc -c <'flflyd.c'`; then
  1252.     echo shar: \"'flflyd.c'\" unpacked with wrong size!
  1253. fi
  1254. # end of 'flflyd.c'
  1255. fi
  1256. if test -f 'flgifw.c' -a "${1}" != "-c" ; then 
  1257.   echo shar: Will not clobber existing file \"'flgifw.c'\"
  1258. else
  1259. echo shar: Extracting \"'flgifw.c'\" \(3572 characters\)
  1260. sed "s/^X//" >'flgifw.c' <<'END_OF_FILE'
  1261. X/*****************************************************************
  1262. X * flgifw.c: FBM Library 0.9 (Beta test) 07-Mar-89  Michael Mauldin
  1263. X *
  1264. X * Portions of this code Copyright (C) 1989 by Michael Mauldin.
  1265. X * Permission is granted to use this file in whole or in part provided
  1266. X * that you do not sell it for profit and that this copyright notice
  1267. X * and the names of all authors are retained unchanged.
  1268. X *
  1269. X * flgifw.c:
  1270. X *
  1271. X * CONTENTS
  1272. X *    write_gif (image, stream, mstr, mlen)
  1273. X *
  1274. X * HISTORY
  1275. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1276. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  1277. X *
  1278. X * 19-Feb-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1279. X *    Adapted to FBM package.
  1280. X *
  1281. X * 13-Feb-89  David Rowley (mgardi@watdcsu.waterloo.edu)
  1282. X *    GIF encoding modifications.
  1283. X *
  1284. X *    Based on: compress.c - File compression ala IEEE Computer, June 1984.
  1285. X *
  1286. X *    Spencer W. Thomas       (decvax!harpo!utah-cs!utah-gr!thomas)
  1287. X *    Jim McKie               (decvax!mcvax!jim)
  1288. X *    Steve Davies            (decvax!vax135!petsd!peora!srd)
  1289. X *    Ken Turkowski           (decvax!decwrl!turtlevax!ken)
  1290. X *    James A. Woods          (decvax!ihnp4!ames!jaw)
  1291. X *    Joe Orost               (decvax!vax135!petsd!joe)
  1292. X *
  1293. X *****************************************************************/
  1294. X
  1295. X# include <stdio.h>
  1296. X# include "fbm.h"
  1297. X
  1298. Xunsigned char *pixels = NULL;
  1299. Xint rowlen = 0;
  1300. X
  1301. Xint GetGIFPixel ();
  1302. X
  1303. X#ifndef lint
  1304. Xstatic char *fbmid =
  1305. X    "$FBM flgifw.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  1306. X#endif
  1307. X
  1308. Xwrite_gif (image, wfile)
  1309. XFBM *image;
  1310. XFILE *wfile;
  1311. X{ register int i, bits, sum, bkg, clrs;
  1312. X  unsigned char *red, *grn, *blu;
  1313. X  int rint[256], gint[256], bint[256];
  1314. X    
  1315. X  if (image->hdr.planes > 1 || image->hdr.clrlen == 0)
  1316. X  { fprintf (stderr, "write_gif can only handle mapped color images\n");
  1317. X    return (0);
  1318. X  }
  1319. X
  1320. X  if (image->hdr.aspect < 1.15 || image->hdr.aspect > 1.25)
  1321. X  { fprintf (stderr,
  1322. X     "Warning, image has aspect ratio of %1.3lf, GIF standard is 1.2\n",
  1323. X     image->hdr.aspect);
  1324. X  }
  1325. X
  1326. X  clrs = image->hdr.clrlen / 3;
  1327. X  
  1328. X  /* Calculate bits per pixel in colormap */
  1329. X  for (i=clrs, bits=1; i > 2; )
  1330. X  { i >>= 1; bits++; }
  1331. X
  1332. X  if (1 << bits != clrs)
  1333. X  { fprintf (stderr, "Error, number of colors %d is not a power of 2\n",
  1334. X         clrs);
  1335. X    return (0);
  1336. X  }
  1337. X  
  1338. X  if (bits < 1 || bits > 8)
  1339. X  { fprintf (stderr, "Error, bits per pixel (%d) must be in range 1..8\n",
  1340. X         bits);
  1341. X    return (0);
  1342. X  }
  1343. X  
  1344. X  red = image->cm;
  1345. X  grn = red + clrs;
  1346. X  blu = grn + clrs;
  1347. X
  1348. X  pixels = image->bm;
  1349. X  rowlen = image->hdr.rowlen;
  1350. X  
  1351. X  /* Copy colormap, and find darkest pixel for background */
  1352. X  { bkg = 0; sum = 1e9;
  1353. X
  1354. X    for (i=0; i<clrs; i++)
  1355. X    { rint[i] = red[i];
  1356. X      gint[i] = grn[i];
  1357. X      bint[i] = blu[i];
  1358. X
  1359. X      if (red[i] + grn[i] + blu[i] < sum)
  1360. X      { bkg = i; sum = red[i] + grn[i] + blu[i]; }
  1361. X    }
  1362. X  }
  1363. X
  1364. X  fprintf (stderr, "Writing GIF file [%dx%d], %d colors, %d bits, bkg %d\n",
  1365. X      image->hdr.cols, image->hdr.rows, clrs, bits, bkg);
  1366. X
  1367. X# ifdef DEBUG
  1368. X  fprintf (stderr, "\n\nColormap:\n");
  1369. X  for (i=0; i<clrs; i++)
  1370. X  { fprintf (stderr, "%5d: <%3d, %3d, %3d>\n",
  1371. X         i, rint[i], gint[i], bint[i]);
  1372. X  }
  1373. X# endif
  1374. X
  1375. X  return (GIFEncode (
  1376. X          wfile,
  1377. X          image->hdr.cols,        /* width */
  1378. X          image->hdr.rows,        /* height */
  1379. X          0,            /* No interlacing */
  1380. X          bkg,            /* Index of Backgrounf */
  1381. X          bits,            /* Bits Per pixel */
  1382. X          rint,            /* Red colormap */
  1383. X          gint,            /* Green colormap */
  1384. X          bint,            /* Blue colormap */
  1385. X          GetGIFPixel ) );        /* Get Pixel value */
  1386. X}
  1387. X
  1388. X/* Returns value of next pixel */
  1389. X
  1390. XGetGIFPixel (x, y)
  1391. Xint x, y;
  1392. X{
  1393. X  return (pixels[y * rowlen + x]);
  1394. X}
  1395. END_OF_FILE
  1396. if test 3572 -ne `wc -c <'flgifw.c'`; then
  1397.     echo shar: \"'flgifw.c'\" unpacked with wrong size!
  1398. fi
  1399. # end of 'flgifw.c'
  1400. fi
  1401. if test -f 'flrdfb.c' -a "${1}" != "-c" ; then 
  1402.   echo shar: Will not clobber existing file \"'flrdfb.c'\"
  1403. else
  1404. echo shar: Extracting \"'flrdfb.c'\" \(4656 characters\)
  1405. sed "s/^X//" >'flrdfb.c' <<'END_OF_FILE'
  1406. X/*****************************************************************
  1407. X * flrdfb.c: FBM Library 0.9 (Beta test) 07-Mar-89  Michael Mauldin
  1408. X *
  1409. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  1410. X * use this file in whole or in part provided that you do not sell it
  1411. X * for profit and that this copyright notice is retained unchanged.
  1412. X *
  1413. X * flrdfb.c: 
  1414. X *
  1415. X * CONTENTS
  1416. X *    read_fbm (image, rfile, mstr, mlen)
  1417. X *    read_hdr_fbm (image, rfile, mstr, mlen)
  1418. X *
  1419. X * EDITLOG
  1420. X *    LastEditDate = Tue Mar  7 19:57:26 1989 - Michael Mauldin
  1421. X *    LastFileName = /usr2/mlm/src/misc/fbm/flrdfb.c
  1422. X *
  1423. X * HISTORY
  1424. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1425. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  1426. X *
  1427. X * 12-Nov-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  1428. X *    Created.
  1429. X *****************************************************************/
  1430. X
  1431. X# include <stdio.h>
  1432. X# include <math.h>
  1433. X# include <ctype.h>
  1434. X# include "fbm.h"
  1435. X
  1436. X/****************************************************************
  1437. X * read_fbm: Read an FBM format bitmap into memory
  1438. X ****************************************************************/
  1439. X
  1440. X#ifndef lint
  1441. Xstatic char *fbmid =
  1442. X    "$FBM flrdfb.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  1443. X#endif
  1444. X
  1445. Xread_fbm (image, rfile, mstr, mlen)
  1446. Xregister FBM *image;
  1447. Xregister FILE *rfile;
  1448. Xchar *mstr;
  1449. Xint mlen;
  1450. X{ register int j, k, rowlen, plnlen;
  1451. X  register unsigned char *bmptr;
  1452. X
  1453. X  if (!read_hdr_fbm (image, rfile, mstr, mlen))
  1454. X  { return (0); }
  1455. X
  1456. X  alloc_fbm (image);
  1457. X
  1458. X  rowlen = image->hdr.rowlen;
  1459. X  plnlen = image->hdr.plnlen;
  1460. X
  1461. X  if (image->hdr.clrlen >  0)
  1462. X  { if (! fread (image->cm, image->hdr.clrlen, 1, rfile))
  1463. X    { fprintf (stderr, "can't read colormap (%d bytes)\n", image->hdr.clrlen);
  1464. X      return (0);
  1465. X    }
  1466. X  }
  1467. X
  1468. X  for (k=0; k<image->hdr.planes; k++)
  1469. X  { bmptr = &(image->bm[k*plnlen]);
  1470. X
  1471. X    for (j=0; j < image->hdr.rows; j++, bmptr += rowlen)
  1472. X    { if (fread (bmptr, 1, rowlen, rfile) != rowlen)
  1473. X      { fprintf (stderr, "premature EOF on input\n");
  1474. X        return (0);
  1475. X      }
  1476. X    }
  1477. X  }
  1478. X    
  1479. X  return (1);
  1480. X}
  1481. X
  1482. X/****************************************************************
  1483. X * read_hdr_fbm: Read an FBM format bitmap header into memory
  1484. X ****************************************************************/
  1485. X
  1486. Xread_hdr_fbm (image, rfile, mstr, mlen)
  1487. Xregister FBM *image;
  1488. Xregister FILE *rfile;
  1489. Xchar *mstr;
  1490. Xint mlen;
  1491. X{ FBMFILEHDR file_hdr;
  1492. X  register char *hp;
  1493. X
  1494. X  hp = (char *) &file_hdr;
  1495. X
  1496. X  if (mlen > 0) strncpy (hp, mstr, mlen);
  1497. X
  1498. X  if (! fread (hp+mlen, sizeof (file_hdr) - mlen, 1, rfile))
  1499. X  { perror ("read_fbm (header)"); return (0); }
  1500. X
  1501. X  if (strncmp (FBM_MAGIC, file_hdr.magic, 2) != 0)
  1502. X  { fprintf (stderr, "Bad magic number, input is not an FBM image\n");
  1503. X    return (0);
  1504. X  }
  1505. X
  1506. X  image->hdr.cols = atoi (file_hdr.cols);
  1507. X  image->hdr.rows = atoi (file_hdr.rows);
  1508. X  image->hdr.planes = atoi (file_hdr.planes);
  1509. X  image->hdr.bits = atoi (file_hdr.bits);
  1510. X  image->hdr.physbits = atoi (file_hdr.physbits);
  1511. X  image->hdr.rowlen = atoi (file_hdr.rowlen);
  1512. X  image->hdr.plnlen = atoi (file_hdr.plnlen);
  1513. X  image->hdr.clrlen = atoi (file_hdr.clrlen);
  1514. X  image->hdr.aspect = atof (file_hdr.aspect);
  1515. X  strncpy (image->hdr.title, file_hdr.title, FBM_MAX_TITLE);
  1516. X  strncpy (image->hdr.credits, file_hdr.credits, FBM_MAX_TITLE);
  1517. X    
  1518. X  if (image->hdr.cols < 1 || image->hdr.cols > 32767)
  1519. X  { fprintf (stderr, "Invalid number of cols (%d) on input\n",
  1520. X         image->hdr.cols);
  1521. X    return (0);
  1522. X  }
  1523. X
  1524. X  if (image->hdr.rows < 1 || image->hdr.rows > 32767)
  1525. X  { fprintf (stderr, "Invalid number of rows (%d) on input\n",
  1526. X         image->hdr.rows);
  1527. X    return (0);
  1528. X  }
  1529. X
  1530. X  if (image->hdr.planes != 1 && image->hdr.planes != 3)
  1531. X  { fprintf (stderr, "Invalid number of planes (%d) on input %s\n",
  1532. X         image->hdr.planes, "(must be 1 or 3)");
  1533. X    return (0);
  1534. X  }
  1535. X
  1536. X  if (image->hdr.bits < 1 || image->hdr.bits > 8)
  1537. X  { fprintf (stderr, "Invalid number of bits (%d) on input %s\n",
  1538. X         image->hdr.bits, "(must be [1..8])");
  1539. X    return (0);
  1540. X  }
  1541. X
  1542. X  if (image->hdr.physbits != 1 && image->hdr.physbits != 8)
  1543. X  { fprintf (stderr, "Invalid number of physbits (%d) on input %s\n",
  1544. X         image->hdr.physbits, "(must be 1 or 8)");
  1545. X    return (0);
  1546. X  }
  1547. X
  1548. X  if (image->hdr.rowlen < 1 || image->hdr.rowlen > 32767)
  1549. X  { fprintf (stderr, "Invalid row length (%d) on input\n",
  1550. X         image->hdr.rowlen);
  1551. X    return (0);
  1552. X  }
  1553. X
  1554. X  if (image->hdr.planes > 1 && image->hdr.plnlen < 1)
  1555. X  { fprintf (stderr, "Invalid plane length (%d) on input\n",
  1556. X         image->hdr.plnlen);
  1557. X    return (0);
  1558. X  }
  1559. X
  1560. X  if (image->hdr.aspect < 0.01 || image->hdr.aspect > 100.0)
  1561. X  { fprintf (stderr, "Invalid aspect ratio %lg on input\n",
  1562. X         image->hdr.aspect);
  1563. X    return (0);
  1564. X  }
  1565. X
  1566. X  return (1);
  1567. X}
  1568. END_OF_FILE
  1569. if test 4656 -ne `wc -c <'flrdfb.c'`; then
  1570.     echo shar: \"'flrdfb.c'\" unpacked with wrong size!
  1571. fi
  1572. # end of 'flrdfb.c'
  1573. fi
  1574. if test -f 'flread.c' -a "${1}" != "-c" ; then 
  1575.   echo shar: Will not clobber existing file \"'flread.c'\"
  1576. else
  1577. echo shar: Extracting \"'flread.c'\" \(4300 characters\)
  1578. sed "s/^X//" >'flread.c' <<'END_OF_FILE'
  1579. X/*****************************************************************
  1580. X * flread.c: FBM Library 0.9 (Beta test) 07-Mar-89  Michael Mauldin
  1581. X *
  1582. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  1583. X * use this file in whole or in part provided that you do not sell it
  1584. X * for profit and that this copyright notice is retained unchanged.
  1585. X *
  1586. X * flread.c: 
  1587. X *
  1588. X * CONTENTS
  1589. X *    read_bitmap (image, rfname)
  1590. X *    write_bitmap (image, wfile, type)
  1591. X *
  1592. X * EDITLOG
  1593. X *    LastEditDate = Tue Mar  7 19:57:27 1989 - Michael Mauldin
  1594. X *    LastFileName = /usr2/mlm/src/misc/fbm/flread.c
  1595. X *
  1596. X * HISTORY
  1597. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1598. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  1599. X *
  1600. X * 28-Nov-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  1601. X *    Created.
  1602. X *****************************************************************/
  1603. X
  1604. X# include <stdio.h>
  1605. X# include "fbm.h"
  1606. X
  1607. X# define BM_MAGC    '!'    /* bm format (!!) */
  1608. X# define FBM_MAGC    '%'    /* fbm format (%bitmap) */
  1609. X# define SUN_MAGC    0x59    /* Sun rasterfile (0x59a66a95) */
  1610. X# define PBM_MAGC    'P'    /* pbm file (P1) */
  1611. X# define ATK_MAGC    '\\'    /* ATK file (\begindata{raster,length}) */
  1612. X# define MP_MAGC    '\0'    /* MacPaint (titlength in short) */
  1613. X# define X11_MAGC    '#'    /* X bitmaps (#define) */
  1614. X# define PCX_MAGC    0xa    /* PCX, PC Paintbrush files */
  1615. X# define IFF_MAGC    'F'    /* Amiga IFF format ("FORM") */
  1616. X# define GIF_MAGC    'G'    /* GIF format (CompuServe) */
  1617. X
  1618. X# define COMPRESSED_CHAR 0x1f    /* Compressed file (0x1f9d) */
  1619. X
  1620. X#ifndef lint
  1621. Xstatic char *fbmid =
  1622. X    "$FBM flread.c <0.9> 07-Mar-89  (C) 1989 by Michael Mauldin$";
  1623. X#endif
  1624. X
  1625. Xread_bitmap (image, fname)
  1626. XFBM *image;
  1627. Xchar *fname;
  1628. X{ int peekch, result = 0, do_pclose = 0;
  1629. X  FILE *rfile;
  1630. X  char cmd[256], magic[32], mlen = 0;
  1631. X
  1632. X  /* Open the file if name given, otherwise assume stdin */
  1633. X  if (fname == NULL || *fname == '\0' || !strcmp (fname, "-"))
  1634. X  { rfile = stdin; }
  1635. X  else
  1636. X  { if ((rfile = fopen (fname, "r")) == NULL)
  1637. X    { perror (fname);  return (0); }
  1638. X  }
  1639. X
  1640. X  /* Guess image type by reading the first character */
  1641. X  peekch = fgetc (rfile);
  1642. X
  1643. X  /* If the image is compressed, uncompress it while reading */  
  1644. X  if (peekch == COMPRESSED_CHAR)
  1645. X  { if (rfile == stdin)
  1646. X    { if (lseek (fileno (rfile), 0L, 0) < 0)  perror ("lseek");
  1647. X      rfile = popen ("uncompress", "r");
  1648. X    }
  1649. X    else
  1650. X    { fclose (rfile);
  1651. X      sprintf (cmd, "uncompress < %s", fname);
  1652. X      rfile = popen (cmd, "r");
  1653. X    }
  1654. X    do_pclose++;
  1655. X
  1656. X    peekch = fgetc (rfile);
  1657. X  }
  1658. X  
  1659. X  magic[0] = peekch;
  1660. X  mlen = 1;
  1661. X
  1662. X  /* Dispatch on the magic character */
  1663. X  switch (peekch)
  1664. X  { case BM_MAGC:    result = read_face (image, rfile, magic, mlen); break;
  1665. X    case FBM_MAGC:    result = read_fbm (image, rfile, magic, mlen); break;
  1666. X    case SUN_MAGC:    result = read_sun (image, rfile, magic, mlen); break;
  1667. X    case PBM_MAGC:    result = read_pbm (image, rfile, magic, mlen); break;
  1668. X    case PCX_MAGC:    result = read_pcx (image, rfile, magic, mlen); break;
  1669. X    case GIF_MAGC:    result = read_gif (image, rfile, magic, mlen); break;
  1670. X    case IFF_MAGC:    result = read_iff (image, rfile, magic, mlen); break;
  1671. X    case ATK_MAGC:    fprintf (stderr, "Can't read Andrew rasters\n"); break;
  1672. X    case MP_MAGC:    fprintf (stderr, "Can't read MacPaint files\n"); break;
  1673. X    case X11_MAGC:    fprintf (stderr, "Can't read X bitmaps\n"); break;
  1674. X    case EOF:        fprintf (stderr, "Empty file"); break;
  1675. X    default:        fprintf (stderr, "Unknown magic char %03o\n", peekch);
  1676. X  }
  1677. X  
  1678. X  if (do_pclose)    pclose (rfile);
  1679. X  else            fclose (rfile);
  1680. X  
  1681. X  return (result);
  1682. X}
  1683. X
  1684. X/****************************************************************
  1685. X * write_bitmap: Write a specified format
  1686. X ****************************************************************/
  1687. X
  1688. Xwrite_bitmap (image, wfile, type)
  1689. XFBM *image;
  1690. XFILE *wfile;
  1691. Xint type;
  1692. X{
  1693. X  switch (type)
  1694. X  {
  1695. X    case FMT_PBM:    if (! write_pbm (image, wfile)) return (0); break;
  1696. X    case FMT_FBM:    if (! write_fbm (image, wfile)) return (0); break;
  1697. X    case FMT_FACE:    if (! write_face (image, wfile)) return (0); break;
  1698. X    case FMT_SUN:    if (! write_sun (image, wfile)) return (0); break;
  1699. X    case FMT_GIF:    if (! write_gif (image, wfile)) return (0); break;
  1700. X    case FMT_IFF:    if (! write_iff (image, wfile)) return (0); break;
  1701. X    default:        fprintf (stderr,  
  1702. X                 "write_bitmap: unknown format type %d\n",
  1703. X                 type);
  1704. X                return (0);
  1705. X  }
  1706. X  
  1707. X  return (1);
  1708. X}
  1709. END_OF_FILE
  1710. if test 4300 -ne `wc -c <'flread.c'`; then
  1711.     echo shar: \"'flread.c'\" unpacked with wrong size!
  1712. fi
  1713. # end of 'flread.c'
  1714. fi
  1715. if test -f 'raw2fbm.c' -a "${1}" != "-c" ; then 
  1716.   echo shar: Will not clobber existing file \"'raw2fbm.c'\"
  1717. else
  1718. echo shar: Extracting \"'raw2fbm.c'\" \(3540 characters\)
  1719. sed "s/^X//" >'raw2fbm.c' <<'END_OF_FILE'
  1720. X/*****************************************************************
  1721. X * raw2fbm.c: FBM Library 0.94 (Beta test) 20-May-89  Michael Mauldin
  1722. X *
  1723. X * Copyright (C) 1989 by Michael Mauldin.  Permission is granted to
  1724. X * use this file in whole or in part provided that you do not sell it
  1725. X * for profit and that this copyright notice is retained unchanged.
  1726. X *
  1727. X * raw2fbm.c: Convert raw format (for example Amiga rasters)
  1728. X *
  1729. X * USAGE
  1730. X *     % raw2fbm -t'title'
  1731. X *           -c'credits'
  1732. X *           -a<aspect>
  1733. X *           -w<width>
  1734. X *           -h<height>
  1735. X *           -d'<planes>    < rawfile > fbm
  1736. X *
  1737. X * EDITLOG
  1738. X *    LastEditDate = Sat May 20 19:07:44 1989 - Michael Mauldin
  1739. X *    LastFileName = /usr2/mlm/src/misc/fbm/raw2fbm.c
  1740. X *
  1741. X * HISTORY
  1742. X * 20-May-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1743. X *    Bug fix from Dave Cohrs <dave@cs.wisc.edu>
  1744. X *
  1745. X * 07-Mar-89  Michael Mauldin (mlm) at Carnegie Mellon University
  1746. X *    Beta release (version 0.9) mlm@cs.cmu.edu
  1747. X *
  1748. X * 20-Aug-88  Michael Mauldin (mlm) at Carnegie-Mellon University
  1749. X *    Created.
  1750. X *****************************************************************/
  1751. X
  1752. X# include <stdio.h>
  1753. X# include "fbm.h"
  1754. X
  1755. X# define USAGE \
  1756. X"Usage: raw2fbm [ -t'title' -c'credits' -a<aspect>\n\
  1757. X         -w<width> -h<height> -d'<planes> ] < rawfile > fbm"
  1758. X
  1759. X#ifndef lint
  1760. Xstatic char *fbmid =
  1761. X    "$FBM raw2fbm.c <0.94> 20-May-89  (C) 1989 by Michael Mauldin$";
  1762. X#endif
  1763. X
  1764. Xmain (argc, argv)
  1765. Xchar *argv[];
  1766. X{ register int j, k, rowlen;
  1767. X  double aspect = 1.2;    /* Default for Digiview 640x400 bitmaps */
  1768. X  int rows = 400, cols = 640, planes = 1;
  1769. X  FBMHDR hdr;
  1770. X  unsigned char *buf;
  1771. X  char title[FBM_MAX_TITLE], credits[FBM_MAX_TITLE];
  1772. X
  1773. X  title[0] = '\0';
  1774. X  credits[0] = '\0';
  1775. X
  1776. X  /* Get the options */
  1777. X  while (--argc > 0 && (*++argv)[0] == '-')
  1778. X  { while (*++(*argv))
  1779. X    { switch (**argv)
  1780. X      { case 'a':    aspect  = atof (*argv+1); SKIPARG; break;
  1781. X    case 'w':    cols   = atoi (*argv+1); SKIPARG; break;
  1782. X    case 'h':    rows  = atoi (*argv+1); SKIPARG; break;
  1783. X    case 'd':    planes   = atoi (*argv+1); SKIPARG; break;
  1784. X    case 't':    strncpy (title, *argv+1, FBM_MAX_TITLE);
  1785. X            title[FBM_MAX_TITLE-1] = '\0';
  1786. X            CLRARG; break;
  1787. X    case 'c':    strncpy (credits, *argv+1, FBM_MAX_TITLE);
  1788. X            credits[FBM_MAX_TITLE-1] = '\0';
  1789. X            CLRARG; break;
  1790. X    default:    fprintf (stderr, "%s\n", USAGE);
  1791. X            exit (1);
  1792. X      }
  1793. X    }
  1794. X  }
  1795. X
  1796. X  if (argc > 0)        cols = atoi (argv[0]);
  1797. X  if (argc > 1)        rows = atoi (argv[1]);
  1798. X  if (argc > 2)        planes = atoi (argv[2]);
  1799. X  if (argc > 3)        aspect = atof (argv[3]);
  1800. X  
  1801. X  if (cols < 1 || rows < 1)
  1802. X  { fprintf (stderr, "Both width (%d) and height (%d) must be positive\n",
  1803. X         cols, rows);
  1804. X    exit (1);
  1805. X  }
  1806. X
  1807. X  if (planes != 1 && planes != 3)
  1808. X  { fprintf (stderr, "Depth must be 1 for B+W or 3 for RGB color\n");
  1809. X    exit (1);
  1810. X  }
  1811. X
  1812. X  if (aspect < 0.01 || aspect > 100.0)
  1813. X  { fprintf (stderr, "Pixel aspect ratio (%lg) must be in [0.01 to 100.0]\n",
  1814. X         aspect);
  1815. X    exit (1);
  1816. X  }
  1817. X
  1818. X  rowlen = 2 * ((cols * 8 + 15) / 16);
  1819. X
  1820. X  /* Build header */
  1821. X  hdr.rows = rows;
  1822. X  hdr.cols = cols;
  1823. X  hdr.planes = planes;
  1824. X  hdr.bits = 8;
  1825. X  hdr.physbits = 8;
  1826. X  hdr.rowlen = rowlen;
  1827. X  hdr.plnlen = hdr.rowlen * rows;
  1828. X  hdr.clrlen = 0;
  1829. X  hdr.aspect = aspect;
  1830. X  strcpy (hdr.title, title);
  1831. X  strcpy (hdr.credits, credits);
  1832. X  
  1833. X  write_hdr_fbm (&hdr, stdout);
  1834. X  
  1835. X  buf = (unsigned char *) malloc (cols);
  1836. X  
  1837. X  for (k=0; k<planes; k++)
  1838. X  { for (j=0; j<rows; j++)  
  1839. X    { if (! fread (buf, cols, 1, stdin))
  1840. X      { fprintf (stdout, "premature end of file on input\n");
  1841. X        exit (1);
  1842. X      }
  1843. X
  1844. X      if (! fwrite (buf, rowlen, 1, stdout))
  1845. X      { perror ("raw2fbm"); exit (1); }
  1846. X    }
  1847. X  }
  1848. X  
  1849. X  exit (0);
  1850. X}
  1851. END_OF_FILE
  1852. if test 3540 -ne `wc -c <'raw2fbm.c'`; then
  1853.     echo shar: \"'raw2fbm.c'\" unpacked with wrong size!
  1854. fi
  1855. # end of 'raw2fbm.c'
  1856. fi
  1857. echo shar: End of archive 3 \(of 8\).
  1858. cp /dev/null ark3isdone
  1859. MISSING=""
  1860. for I in 1 2 3 4 5 6 7 8 ; do
  1861.     if test ! -f ark${I}isdone ; then
  1862.     MISSING="${MISSING} ${I}"
  1863.     fi
  1864. done
  1865. if test "${MISSING}" = "" ; then
  1866.     echo You have unpacked all 8 archives.
  1867.     rm -f ark[1-9]isdone
  1868. else
  1869.     echo You still need to unpack the following archives:
  1870.     echo "        " ${MISSING}
  1871. fi
  1872. ##  End of shell archive.
  1873. exit 0
  1874.